﻿// Copyright (c) 2012 - 2020 Jared Zheng <jaredz at outlook dot com>
// Buddha Framework is licensed under Mulan PSL v2.
// You can use this software according to the terms and conditions of the Mulan PSL v2.
// You may obtain a copy of Mulan PSL v2 at:
//          http://license.coscl.org.cn/MulanPSL2
// THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
// EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
// MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
//
// Create : 2012-12-01 version 0.1 Jared Zheng <jaredz at outlook dot com>
// Update : 2018-12-05 version 3.1.5 Jared Zheng <jaredz at outlook dot com>

#ifndef __SERVER_CONFIG_H__
#define __SERVER_CONFIG_H__

#pragma once

#include "filelog.h"
#include "filepath.h"
#include "keyvalue.h"
#include "markup.h"

///////////////////////////////////////////////////////////////////////////////////////////////////////////
/// 通用配置
class NOVTABLE CServerConfig : public MObject
{
public:
    /// 配置参数定义
    enum CFG_LOAD
    {
        // load server
        CFG_LOAD_NONE       = 0x00000000,
        CFG_LOAD_CENTER     = 0x00000001, ///< 加载同步管理服务器
        CFG_LOAD_BALANCE    = 0x00000002, ///< 加载授权均衡服务器
        CFG_LOAD_AUTHORDB   = 0x00000004, ///< 加载授权数据服务器
        CFG_LOAD_AUTHOR     = 0x00000008, ///< 加载授权网关服务器
        CFG_LOAD_MASTERDB   = 0x00000010, ///< 加载业务数据服务器
        CFG_LOAD_MASTER     = 0x00000020, ///< 加载业务管理服务器
        CFG_LOAD_SERVICE    = 0x00000040, ///< 加载业务功能服务器
        CFG_LOAD_GATE       = 0x00000080, ///< 加载业务网关服务器
        CFG_LOAD_ALLSERVER  = 0x000000FF, ///< 加载全部服务器
        CFG_LOAD_NDBSERVER  = 0x000000EB,
        CFG_LOAD_ALLCOUNT   = 8,
    };

    enum CFG_PORT
    {
        CFG_CENTER_PORT     = 11100, ///< 同步管理服务器默认监听端口(授权均衡, 授权网关, 业务管理)
        CFG_AUTHORDB_PORT   = 11200, ///< 授权数据服务器默认监听端口(授权网关) 
        CFG_MASTERDB_PORT   = 11300, ///< 业务数据服务器默认监听端口(业务管理, 业务功能)
        CFG_MASTER_PORT     = 11400, ///< 业务管理服务器默认监听端口(业务功能, 业务网关)
        CFG_BALANCE_PORT    = 16000, ///< 授权均衡服务器默认UDP端口(外网端)
        CFG_AUTHOR_PORT     = 16100, ///< 授权网关服务器默认监听端口(外网端) 
        CFG_GATE_PORT       = 16200, ///< 业务网关服务器默认监听端口(外网端)
    };

    enum CFG_TIME
    {
        CFG_TIME_UPDATE_ID  = 30,
        CFG_UPDATE_MIN_TIME = 15,           ///< 同步更新最小周期[秒]
        CFG_UPDATE_DEF_TIME = 15,           ///< 同步更新默认周期[秒]
        CFG_STAT_MIN_TIME   = 15 * 60,      ///< 信息统计最小周期15分钟[秒]
        CFG_STAT_DEF_TIME   = 30 * 60,      ///< 信息统计默认周期30分钟[秒]
        CFG_STAT_MAX_TIME   = 24 * 60 * 60, ///< 最大每天统计一次[秒]
    };
    static CPCXStr ServerConfig;          ///< 配置
    static CPCXStr NetworkPtr;            ///< 网络

    static CPCXStr ConfigName;            ///< 默认配置文件名称
    static CPCXStr ConfigServer;          ///< 命令行配置服务器名称

    static CPCXStr NetworkConfig;         ///< NetworkConfig
    static CPCXStr NetworkAttr;           ///< NetworkAttr=0(0表示使用默认值, 后面的都忽略)
    static CPCXStr NetworkThread;         ///< NetworkThread=0(cores)
    static CPCXStr NetworkAck;            ///< NetworkAck(连接完成握手包时间)
    static CPCXStr NetworkTimeout;        ///< NetworkTimeout(心跳包时间间隔)
    static CPCXStr NetworkBuffer;         ///< NetworkBuffer
    static CPCXStr NetworkJumbo;          ///< NetworkJumbo

    static CPCXStr ServersCommon;         ///< ServersCommon
    static CPCXStr UpdateTick;            ///< UpdateTick=30(秒)
    static CPCXStr StatTick;              ///< StatTick=15(分)
    static CPCXStr AnyListen;             ///< 是否支持所有地址都监听模式
    static CPCXStr InfoDump;              ///< 是否同步服务器信息输出信息
    static CPCXStr LoadServers;           ///< 加载的服务器种类 : LoadServers=CenterServer|BalanceServer
    static CPCXStr CenterServer;          ///< 同步管理服务器模块路径
    static CPCXStr BalanceServer;         ///< 授权均衡服务器模块路径
    static CPCXStr AuthorDBServer;        ///< 授权数据服务器模块路径
    static CPCXStr AuthorServer;          ///< 授权网关服务器模块路径
    static CPCXStr MasterDBServer;        ///< 业务数据服务器模块路径
    static CPCXStr MasterServer;          ///< 业务管理服务器模块路径
    static CPCXStr ServiceServer;         ///< 业务功能服务器模块路径
    static CPCXStr GateServer;            ///< 业务网关服务器模块路径

    static CPCXStr CenterRoutine;         ///< 同步管理框架例程默认名称
    static CPCXStr BalanceRoutine;        ///< 授权均衡框架例程默认名称
    static CPCXStr AuthorDBRoutine;       ///< 授权数据框架例程默认名称
    static CPCXStr AuthorRoutine;         ///< 授权网关框架例程默认名称
    static CPCXStr MasterDBRoutine;       ///< 业务数据框架例程默认名称
    static CPCXStr MasterRoutine;         ///< 业务管理框架例程默认名称
    static CPCXStr ServiceRoutine;        ///< 业务功能框架例程默认名称
    static CPCXStr GateRoutine;           ///< 业务网关框架例程默认名称

    static CPCXStr Value;
    static CPCXStr Internal;
    static CPCXStr External;
    static CPCXStr Ip;                    ///< 要和NetworkAttr中ipv4 or ipv6匹配
    static CPCXStr Port;                  ///< 端口
    static CPCXStr Id;                    ///< Id
    static CPCXStr Incr;                  ///< 增长
    static CPCXStr ExtConfig;             ///< 服务器扩展配置文件路径
    static CPCXStr LocalHost;             ///< 本地地址
    static CPCXStr AddrAnyV4;             ///< ipv4 addr-any
    static CPCXStr AddrAnyV6;             ///< ipv6 addr-any
    static CPCXStr LogFolder;             ///< log日志目录
    static CPCXStr CurFolder;             ///< 当前目录
    static CPCXStr LibPrefix;             ///< 模块文件前缀
    static CPCXStr LibExt;                ///< 模块文件后缀
    static XChar   PathSepChar;           ///<

    typedef CTMap<CString, CString>         STR_ARGV, *PSTR_ARGV;
    typedef CTMap<CString, CString>::PAIR   STR_ARGV_PAIR;
public:
    CServerConfig(void);
    ~CServerConfig(void);
    /// 获取文件管理器
    CFilePath& GetFilePath(void);
    /// 获取key-value管理器
    CKeyValue& GetKeyValue(void);

    void   SetArgs(PCXStr pszCmd);
    void   SetArgs(Int nArgc, PXStr* ppszArgv);

    /// 初始化
    bool   Init(void);
    /// 重新从配置文件加载
    void   Update(void);
    /// 退出
    void   Exit(void);
    /// 打印配置信息到文件日志
    void   Dump(CFileLog& Log, Int nServer);

    /// 获取网络层配置参数-属性
    Int    GetNetworkAttr(void);
    /// 获取网络层配置参数-线程数量
    Int    GetNetworkThread(void);
    /// 获取网络层配置参数-ACK时间
    Int    GetNetworkAck(void);
    /// 获取网络层配置参数-超时时间
    Int    GetNetworkTimeout(void);
    /// 获取网络层配置参数-普通接收或者发送缓存大小
    Int    GetNetworkBuffer(void);
    /// 获取网络层配置参数-巨帧接收或者发送缓存大小
    Int    GetNetworkJumbo(void);

    /// 获取同步服务器数据间隔
    Int    GetUpdateTick(void);
    /// 获取统计信息时间间隔
    Int    GetStatTick(void);
    /// 是否支持所有地址都监听模式, TRUE表示支持
    Int    GetAnyListen(void);
    /// 是否同步服务器信息输出信息, TRUE表示支持
    Int    GetInfoDump(void);
    /// 获取加载服务器情况
    Int    GetLoadServers(void);
    /// 获取各服务器的模块文件路径
    /// @param[in] Int nServer 服务器类型, 参考CFG_LOAD_XXX
    /// @param[out] CStringFix& strPath 文件路径
    bool   GetServerPath(Int nServer, CStringFix& strPath);

    /// 获取各服务器的地址信息
    /// @param[in] Int nServer 服务器类型, 参考CFG_LOAD_XXX
    /// @param[in] Int nServerAddr 服务器类型, 参考CFG_LOAD_XXX
    /// @param[out] CStrAddr& strAddr 地址
    bool   GetServerAddr(Int nServer, Int nServerAddr, CStrAddr& strAddr, bool bAny2Local = false);
    /// 获取各服务器的Id
    UShort GetServerId(Int nServer);
    /// 获取各服务器的负载增长率
    UShort GetServerIncr(Int nServer);
    /// 获取各服务器的事件处理队列线程数
    Int    GetServerValue(Int nServer);
    /// 获取各服务器的扩展配置文件路径
    bool   GetServerExtConfig(Int nServer, CStringFix& strPath);

    PCXStr GetLogPath(void);
private:
    bool LoadConfig(CXMLNode* pRoot);
    bool LoadNetwork(CXMLNode* pRoot);
    bool LoadServersCommon(CXMLNode* pRoot);
    bool LoadCenterServer(CXMLNode* pRoot);
    bool LoadBalanceServer(CXMLNode* pRoot);
    bool LoadAuthorDBServer(CXMLNode* pRoot);
    bool LoadAuthorServer(CXMLNode* pRoot);
    bool LoadMasterDBServer(CXMLNode* pRoot);
    bool LoadMasterServer(CXMLNode* pRoot);
    bool LoadServiceServer(CXMLNode* pRoot);
    bool LoadGateServer(CXMLNode* pRoot);

    bool LoadServersCommon(CStringFix& strFixValue);

    bool LoadValue(CXMLNode* pSection, PCXStr pszElement, PCXStr pszAttr, Int& nValue);
    bool LoadValue(CXMLNode* pSection, PCXStr pszElement, PCXStr pszAttr, CStringFix& strFixValue);

    bool LoadServerAttr(CXMLNode* pSection, Int& nId, Int& nIncr, Int& nValue, CStringFix& strFixExtConfig);
    bool LoadServerAttr(Int& nId, Int& nIncr, Int& nValue, CStringFix& strFixExtConfig, Int nIndex = 0);
    bool LoadServerAddr(CXMLNode* pSection, PCXStr pszServer, CStrAddr& strAddr);
    bool LoadServerAddr(PCXStr pszServer, CStrAddr& strAddr, Int nIndex = 0);

    void ResetNetwork(void);
    void ResetServerCommon(void);
    void ResetCenterServer(bool bReset = true, Int nIndex = 0);
    void ResetBalanceServer(bool bReset = true, Int nIndex = 0);
    void ResetAuthorDBServer(bool bReset = true, Int nIndex = 0);
    void ResetAuthorServer(bool bReset = true, Int nIndex = 0);
    void ResetMasterDBServer(bool bReset = true, Int nIndex = 0);
    void ResetMasterServer(bool bReset = true, Int nIndex = 0);
    void ResetServiceServer(bool bReset = true, Int nIndex = 0);
    void ResetGateServer(bool bReset = true, Int nIndex = 0);

    void CheckConfig(void);
    void CheckAddr(CStrAddr& strAddr, bool bListen = true);
    void CheckExtConfig(CStringFix& strExtConfig, PCXStr pszServer);
    void CheckPath(CStringFix& strPath, PCXStr pszServer);
public:
    CStringFix   m_strConfigName;
    CStringFix   m_strExtConfigPath;
    CStringFix   m_strLogConfigPath;
    // network
    Int          m_nNetworkAttr;    ///< 网络层配置参数-属性
    Int          m_nNetworkThread;  ///< 网络层配置参数-线程数量
    Int          m_nNetworkAck;     ///< 网络层配置参数-ACK时间
    Int          m_nNetworkTimeout; ///< 网络层配置参数-超时时间
    Int          m_nNetworkBuffer;  ///< 网络层配置参数-普通接收或者发送缓存大小
    Int          m_nNetworkJumbo;   ///< 网络层配置参数-巨帧接收或者发送缓存大小
    // servers
    Int          m_nUpdateTick;     ///< 同步服务器数据间隔
    Int          m_nStatTick;       ///< 统计信息时间间隔
    Int          m_nAnyListen;      ///< 是否支持所有地址都监听模式
    Int          m_nInfoDump;       ///< 是否同步服务器信息输出信息
    Int          m_nLoadServers;    ///< 加载服务器情况
    //
    CStringFix   m_strCenterServerPath;
    CStringFix   m_strBalanceServerPath;
    CStringFix   m_strAuthorDBServerPath;
    CStringFix   m_strAuthorServerPath;
    CStringFix   m_strMasterDBServerPath;
    CStringFix   m_strMasterServerPath;
    CStringFix   m_strServiceServerPath;
    CStringFix   m_strGateServerPath;
    // center-server
    CStrAddr     m_CenterServer4;
    Int          m_nCenterServerId;
    Int          m_nCenterServerIncr;
    Int          m_nCenterServerValue;
    CStringFix   m_strCenterServerExtConfig;
    // balance-server
    CStrAddr     m_BalanceServer2;
    CStrAddr     m_BalanceServer4;
    Int          m_nBalanceServerId;
    Int          m_nBalanceServerIncr;
    Int          m_nBalanceServerValue;
    CStringFix   m_strBalanceServerExtConfig;
    // authordb-server
    CStrAddr     m_AuthorDBServer2;
    CStrAddr     m_AuthorDBServer4;
    Int          m_nAuthorDBServerId;
    Int          m_nAuthorDBServerIncr;
    Int          m_nAuthorDBServerValue;
    CStringFix   m_strAuthorDBServerExtConfig;
    // author-server   
    CStrAddr     m_AuthorServer2Center;
    CStrAddr     m_AuthorServer2AuthorDB;
    CStrAddr     m_AuthorServer4Master;
    CStrAddr     m_AuthorServer4External;
    Int          m_nAuthorServerId;
    Int          m_nAuthorServerIncr;
    Int          m_nAuthorServerValue;
    CStringFix   m_strAuthorServerExtConfig;
    // masterdb-server
    CStrAddr     m_MasterDBServer2;
    CStrAddr     m_MasterDBServer4;
    Int          m_nMasterDBServerId;
    Int          m_nMasterDBServerIncr;
    Int          m_nMasterDBServerValue;
    CStringFix   m_strMasterDBServerExtConfig;
    // master-server
    CStrAddr     m_MasterServer2Center;
    CStrAddr     m_MasterServer2MasterDB;
    CStrAddr     m_MasterServer4Author;
    CStrAddr     m_MasterServer4;
    Int          m_nMasterServerId;
    Int          m_nMasterServerIncr;
    Int          m_nMasterServerValue;    ///< = 0表示不需要连接masterdb
    CStringFix   m_strMasterServerExtConfig;
    // service-server
    CStrAddr     m_ServiceServer2Master;
    CStrAddr     m_ServiceServer2MasterDB;
    Int          m_nServiceServerId;
    Int          m_nServiceServerIncr;
    Int          m_nServiceServerValue;
    CStringFix   m_strServiceServerExtConfig;
    // gate-server
    CStrAddr     m_GateServer2;
    CStrAddr     m_GateServer4Author;
    CStrAddr     m_GateServer4External;
    Int          m_nGateServerId;
    Int          m_nGateServerIncr;
    Int          m_nGateServerValue;
    CStringFix   m_strGateServerExtConfig;

    CFilePath    m_FilePath; ///< 文件管理器
    CKeyValue    m_KeyValue; ///< key-value管理器
    STR_ARGV     m_strArgv;
};

INLINE CServerConfig::CServerConfig(void)
: m_strConfigName(ConfigName)
, m_nNetworkAttr(0)
, m_nNetworkThread(0)
, m_nNetworkAck(0)
, m_nNetworkTimeout(0)
, m_nNetworkBuffer(0)
, m_nNetworkJumbo(0)
, m_nUpdateTick(CFG_UPDATE_DEF_TIME)
, m_nStatTick(CFG_STAT_DEF_TIME)
, m_nAnyListen(TRUE)
, m_nInfoDump(TRUE)
, m_nLoadServers(CFG_LOAD_NDBSERVER)
//
, m_CenterServer4(CFG_CENTER_PORT)
, m_nCenterServerId(PAKT_CENTER)
, m_nCenterServerIncr(DATAD_INCR_LOAD)
, m_nCenterServerValue(0)
//
, m_BalanceServer2(0)
, m_BalanceServer4(CFG_BALANCE_PORT)
, m_nBalanceServerId(PAKT_BALANCE)
, m_nBalanceServerIncr(DATAD_INCR_LOAD)
, m_nBalanceServerValue(0)
//
, m_AuthorDBServer2(0)
, m_AuthorDBServer4(0)
, m_nAuthorDBServerId(PAKT_AUTHORDB)
, m_nAuthorDBServerIncr(DATAD_INCR_LOAD)
, m_nAuthorDBServerValue(0)
//
, m_AuthorServer2Center(0)
, m_AuthorServer2AuthorDB(0)
, m_AuthorServer4Master(0)
, m_AuthorServer4External(CFG_AUTHOR_PORT)
, m_nAuthorServerId(PAKT_AUTHOR)
, m_nAuthorServerIncr(DATAD_INCR_LOAD)
, m_nAuthorServerValue(0)
//
, m_MasterDBServer2(0)
, m_MasterDBServer4(0)
, m_nMasterDBServerId(PAKT_MASTERDB)
, m_nMasterDBServerIncr(DATAD_INCR_LOAD)
, m_nMasterDBServerValue(0)
//
, m_MasterServer2Center(0)
, m_MasterServer2MasterDB(0)
, m_MasterServer4Author(0)
, m_MasterServer4(CFG_MASTER_PORT)
, m_nMasterServerId(PAKT_MASTER)
, m_nMasterServerIncr(DATAD_INCR_LOAD)
, m_nMasterServerValue(0)
//
, m_ServiceServer2Master(0)
, m_ServiceServer2MasterDB(0)
, m_nServiceServerId(PAKT_SERVICE)
, m_nServiceServerIncr(DATAD_INCR_LOAD)
, m_nServiceServerValue(0)
//
, m_GateServer2(0)
, m_GateServer4Author(0)
, m_GateServer4External(CFG_GATE_PORT)
, m_nGateServerId(PAKT_GATE)
, m_nGateServerIncr(DATAD_INCR_LOAD)
, m_nGateServerValue(0)
{
}

INLINE CServerConfig::~CServerConfig(void)
{
}

INLINE CFilePath& CServerConfig::GetFilePath(void)
{
    return m_FilePath;
}

INLINE CKeyValue& CServerConfig::GetKeyValue(void)
{
    return m_KeyValue;
}

INLINE Int CServerConfig::GetNetworkAttr(void)
{
    return m_nNetworkAttr;
}

INLINE Int CServerConfig::GetNetworkThread(void)
{
    return m_nNetworkThread;
}

INLINE Int CServerConfig::GetNetworkAck(void)
{
    return m_nNetworkAck;
}

INLINE Int CServerConfig::GetNetworkTimeout(void)
{
    return m_nNetworkTimeout;
}

INLINE Int CServerConfig::GetNetworkBuffer(void)
{
    return m_nNetworkBuffer;
}

INLINE Int CServerConfig::GetNetworkJumbo(void)
{
    return m_nNetworkJumbo;
}

INLINE Int CServerConfig::GetUpdateTick(void)
{
    return m_nUpdateTick;
}

INLINE Int CServerConfig::GetStatTick(void)
{
    return m_nStatTick;
}

INLINE Int CServerConfig::GetAnyListen(void)
{
    return m_nAnyListen;
}

INLINE Int CServerConfig::GetInfoDump(void)
{
    return m_nInfoDump;
}

INLINE Int CServerConfig::GetLoadServers(void)
{
    return m_nLoadServers;
}

INLINE bool CServerConfig::GetServerPath(Int nServer, CStringFix& strPath)
{
    bool bRet = true;
    switch (nServer)
    {
    case CFG_LOAD_CENTER:
        {
            strPath = m_strCenterServerPath;
        }
        break;
    case CFG_LOAD_BALANCE:
        {
            strPath = m_strBalanceServerPath;
        }
        break;
    case CFG_LOAD_AUTHORDB:
        {
            strPath = m_strAuthorDBServerPath;
        }
        break;
    case CFG_LOAD_AUTHOR:
        {
            strPath = m_strAuthorServerPath;
        }
        break;
    case CFG_LOAD_MASTERDB:
        {
            strPath = m_strMasterDBServerPath;
        }
        break;
    case CFG_LOAD_MASTER:
        {
            strPath = m_strMasterServerPath;
        }
        break;
    case CFG_LOAD_SERVICE:
        {
            strPath = m_strServiceServerPath;
        }
        break;
    case CFG_LOAD_GATE:
        {
            strPath = m_strGateServerPath;
        }
        break;
    default:
        {
            bRet = false;
        }
    }
    return bRet;
}

INLINE bool CServerConfig::GetServerAddr(Int nServer, Int nServerAddr, CStrAddr& strAddr, bool bAny2Local)
{
    bool bRet = true;
    switch (nServer)
    {
    case CFG_LOAD_CENTER:
        {
            strAddr = m_CenterServer4;
        }
        break;
    case CFG_LOAD_BALANCE:
        {
            if (nServerAddr == CFG_LOAD_CENTER)
            {
                strAddr = m_BalanceServer2;
            }
            else
            {
                strAddr = m_BalanceServer4;
            }
        }
        break;
    case CFG_LOAD_AUTHORDB:
        {
            if (nServerAddr == CFG_LOAD_CENTER)
            {
                strAddr = m_AuthorDBServer2;
            }
            else
            {
                strAddr = m_AuthorDBServer4;
            }
        }
        break;
    case CFG_LOAD_AUTHOR:
        {
            if (nServerAddr == CFG_LOAD_CENTER)
            {
                strAddr = m_AuthorServer2Center;
            }
            else if (nServerAddr == CFG_LOAD_AUTHORDB)
            {
                strAddr = m_AuthorServer2AuthorDB;
            }
            else if (nServerAddr == CFG_LOAD_MASTER)
            {
                strAddr = m_AuthorServer4Master;
            }
            else
            {
                strAddr = m_AuthorServer4External;
            }
        }
        break;
    case CFG_LOAD_MASTERDB:
        {
            if (nServerAddr == CFG_LOAD_CENTER)
            {
                strAddr = m_MasterDBServer2;
            }
            else
            {
                strAddr = m_MasterDBServer4;
            }
        }
        break;
    case CFG_LOAD_MASTER:
        {
            if (nServerAddr == CFG_LOAD_CENTER)
            {
                strAddr = m_MasterServer2Center;
            }
            else if (nServerAddr == CFG_LOAD_MASTERDB)
            {
                strAddr = m_MasterServer2MasterDB;
            }
            else if (nServerAddr == CFG_LOAD_AUTHOR)
            {
                strAddr = m_MasterServer4Author;
            }
            else
            {
                strAddr = m_MasterServer4;
            }
        }
        break;
    case CFG_LOAD_SERVICE:
        {
            if (nServerAddr == CFG_LOAD_MASTERDB)
            {
                strAddr = m_ServiceServer2MasterDB;
            }
            else
            {
                strAddr = m_ServiceServer2Master;
            }
        }
        break;
    case CFG_LOAD_GATE:
        {
            if (nServerAddr == CFG_LOAD_MASTER)
            {
                strAddr = m_GateServer2;
            }
            else if (nServerAddr == CFG_LOAD_AUTHOR)
            {
                strAddr = m_GateServer4Author;
            }
            else
            {
                strAddr = m_GateServer4External;
            }
        }
        break;
    default:
        {
            //assert(0);
            bRet = false;
        }
    }
    if (bAny2Local && ((strAddr.strIp == AddrAnyV4) || (strAddr.strIp == AddrAnyV6)))
    {
        strAddr.strIp = LocalHost;
    }
    return bRet;
}

INLINE UShort CServerConfig::GetServerId(Int nServer)
{
    Int nRet = 0;
    switch (nServer)
    {
    case CFG_LOAD_CENTER:
        {
            nRet = m_nCenterServerId;
        }
        break;
    case CFG_LOAD_BALANCE:
        {
            nRet = m_nBalanceServerId;
        }
        break;
    case CFG_LOAD_AUTHORDB:
        {
            nRet = m_nAuthorDBServerId;
        }
        break;
    case CFG_LOAD_AUTHOR:
        {
            nRet = m_nAuthorServerId;
        }
        break;
    case CFG_LOAD_MASTERDB:
        {
            nRet = m_nMasterDBServerId;
        }
        break;
    case CFG_LOAD_MASTER:
        {
            nRet = m_nMasterServerId;
        }
        break;
    case CFG_LOAD_SERVICE:
        {
            nRet = m_nServiceServerId;
        }
        break;
    case CFG_LOAD_GATE:
        {
            nRet = m_nGateServerId;
        }
        break;
    default:
        {
            //assert(0);
        }
    }
    return (UShort)nRet;
}

INLINE UShort CServerConfig::GetServerIncr(Int nServer)
{
    Int nRet = 0;
    switch (nServer)
    {
    case CFG_LOAD_CENTER:
        {
            nRet = m_nCenterServerIncr;
        }
        break;
    case CFG_LOAD_BALANCE:
        {
            nRet = m_nBalanceServerIncr;
        }
        break;
    case CFG_LOAD_AUTHORDB:
        {
            nRet = m_nAuthorDBServerIncr;
        }
        break;
    case CFG_LOAD_AUTHOR:
        {
            nRet = m_nAuthorServerIncr;
        }
        break;
    case CFG_LOAD_MASTERDB:
        {
            nRet = m_nMasterDBServerIncr;
        }
        break;
    case CFG_LOAD_MASTER:
        {
            nRet = m_nMasterServerIncr;
        }
        break;
    case CFG_LOAD_SERVICE:
        {
            nRet = m_nServiceServerIncr;
        }
        break;
    case CFG_LOAD_GATE:
        {
            nRet = m_nGateServerIncr;
        }
        break;
    default:
        {
            //assert(0);
        }
    }
    return (UShort)nRet;
}

INLINE Int CServerConfig::GetServerValue(Int nServer)
{
    Int nRet = 0;
    switch (nServer)
    {
    case CFG_LOAD_CENTER:
        {
            nRet = m_nCenterServerValue;
        }
        break;
    case CFG_LOAD_BALANCE:
        {
            nRet = m_nBalanceServerValue;
        }
        break;
    case CFG_LOAD_AUTHORDB:
        {
            nRet = m_nAuthorDBServerValue;
        }
        break;
    case CFG_LOAD_AUTHOR:
        {
            nRet = m_nAuthorServerValue;
        }
        break;
    case CFG_LOAD_MASTERDB:
        {
            nRet = m_nMasterDBServerValue;
        }
        break;
    case CFG_LOAD_MASTER:
        {
            nRet = m_nMasterServerValue;
        }
        break;
    case CFG_LOAD_SERVICE:
        {
            nRet = m_nServiceServerValue;
        }
        break;
    case CFG_LOAD_GATE:
        {
            nRet = m_nGateServerValue;
        }
        break;
    default:
        {
            //assert(0);
        }
    }
    return nRet;
}

INLINE bool CServerConfig::GetServerExtConfig(Int nServer, CStringFix& strPath)
{
    switch (nServer)
    {
    case CFG_LOAD_CENTER:
        {
            strPath = m_strCenterServerExtConfig;
        }
        break;
    case CFG_LOAD_BALANCE:
        {
            strPath = m_strBalanceServerExtConfig;
        }
        break;
    case CFG_LOAD_AUTHORDB:
        {
            strPath = m_strAuthorDBServerExtConfig;
        }
        break;
    case CFG_LOAD_AUTHOR:
        {
            strPath = m_strAuthorServerExtConfig;
        }
        break;
    case CFG_LOAD_MASTERDB:
        {
            strPath = m_strMasterDBServerExtConfig;
        }
        break;
    case CFG_LOAD_MASTER:
        {
            strPath = m_strMasterServerExtConfig;
        }
        break;
    case CFG_LOAD_SERVICE:
        {
            strPath = m_strServiceServerExtConfig;
        }
        break;
    case CFG_LOAD_GATE:
        {
            strPath = m_strGateServerExtConfig;
        }
        break;
    default:
        {
            //assert(0);
        }
    }
    return (strPath.Length() != 0);
}

INLINE PCXStr CServerConfig::GetLogPath(void)
{
    return *m_strLogConfigPath;
}

#endif // __SERVER_CONFIG_H__
